#include "StdAfx.h"
#include "Controller.h"
#include <sstream>
#include <fstream>
#include "RegisterUser.h"
#include "AddAgenda.h"
#include "DeleteAgenda.h"
#include "ParameterException.h"
#include "UnableToOpenFile.h"
#include "ClearAgenda.h"
#include "Message.h"
#include "Date.h"
#include "Parser.h"

Controller* Controller::_controller = 0;
AgendaManager Controller::manager = AgendaManager();

Controller* Controller::getInstance ()
{
	if(_controller == 0)
	{
		_controller = new Controller();
	}
	return _controller;
}

string Controller::handle(string cmdLine)
{

	string cmd;
	vector<string> argv = vector<string>();
	
	if( cmdLine.empty() )
		return "";
	Parser::parse(cmdLine, cmd, argv);

	AgendaCommand* AgendaCmd = 0;
	string returnMsg;

	try
	{

		if(cmd == "register")
		{	
			if(argv.size() != 2)
				throw ParameterException();

			AgendaCmd = new RegisterUser(argv[0], argv[1]);
			manager.doAction(AgendaCmd);
			returnMsg = msg::RegisterSuccess;
		}
		else if(cmd == "add")
		{
			if(argv.size() != 6)
				throw ParameterException();

			AgendaCmd = new AddAgenda(argv[0], argv[1], argv[2], argv[3], argv[4], argv[5]);
			manager.doAction(AgendaCmd);
			returnMsg = msg::AddSuccess;
		}
		else if(cmd == "delete")
		{
			if(argv.size() != 3)
				throw ParameterException();

			AgendaCmd = new DeleteAgenda(argv[0], argv[1], argv[2]);
			manager.doAction(AgendaCmd);
			returnMsg = msg::DeleteSuccess;
		}
		else if(cmd == "clear")
		{
			if(argv.size() != 2)
				throw ParameterException();

			AgendaCmd = new ClearAgenda(argv[0], argv[1]);
			manager.doAction(AgendaCmd);
			returnMsg = msg::ClearSuccess;
		}
		else if(cmd == "query")
		{
			if(argv.size() != 4)
				throw ParameterException();

			vector<Meeting *> meetings = manager.query(argv[0], argv[1], argv[2], argv[3]);
			returnMsg = generateMsg(argv[0], meetings);
		}
		else if(cmd =="batch")				//batch operation option
		{
			string cmdLine2;

			if(argv.size() != 1 )
				throw ParameterException();

			ifstream bat;
			bat.open( argv[0].c_str(), ifstream::in );		//open the batch file

			if( !bat.is_open() )
				throw UnableToOpenFile();

			while( ! bat.eof() )				//excute the every command in every line
			{
				getline(bat, cmdLine2);
				if( cmdLine2 != "" )
				{
					cout<<'$'<<cmdLine2<<endl;
					string returnMsg2 = Controller::getInstance()->handle(cmdLine2);		
					cout<< returnMsg2 <<endl;
				}
			}

			returnMsg = msg::BatchSuccess;
		}
		else if(cmd == "quit")
			returnMsg = "quit";
		else
			returnMsg = "";
	}
	catch(exception& ex)
	{
		returnMsg = ex.what();
	}
	delete AgendaCmd;

	return returnMsg;
}//modify

string Controller::generateMsg(string name, vector<Meeting *>& meetings)
{
	ostringstream oss;
	oss << msg::MeetingListHeader << endl;

	int id = 1;
	for(vector<Meeting *>::iterator it = meetings.begin(); it != meetings.end(); ++it)
	{
		Meeting * m = *it;

		oss << id << '\t'
			<< (*it)->getInviter().getUserName() << '\t'
			<< (*it)->getInvitee().getUserName() << '\t' << '\t'
			<< (*it)->getInterval().getStartTime() << '\t' 
			<< (*it)->getInterval().getEndTime() << '\t' 
			<< (*it)->getTitle() << '\t';
		oss << endl;

		id++;
	}
	return oss.str();
}

Controller::Controller(void)
{
}


Controller::~Controller(void)
{

	delete _controller;
}